require('dotenv').config();
const express = require('express');
const cors = require('cors');
const helmet = require('helmet');
const morgan = require('morgan');
const rateLimit = require('express-rate-limit');
const { errorHandler } = require('./middlewares/errorHandler');
const db = require('./models');
const redis = require('./config/redis');

// 路由
const userRoutes = require('./routes/userRoutes');
const gameRoutes = require('./routes/gameRoutes');
const leaderboardRoutes = require('./routes/leaderboardRoutes');

// 初始化Express应用
const app = express();

// 设置安全头
app.use(helmet());

// 日志中间件
app.use(morgan('dev'));

// 跨域设置
app.use(cors());

// 解析JSON
app.use(express.json());

// 限流中间件
const apiLimiter = rateLimit({
  windowMs: 15 * 60 * 1000, // 15分钟
  max: 100, // 每个IP限制100个请求
  standardHeaders: true,
  legacyHeaders: false,
});

// 应用限流
app.use('/api/', apiLimiter);

// 健康检查
app.get('/health', (req, res) => {
  res.status(200).json({ status: 'ok' });
});

// 路由
app.use('/api/users', userRoutes);
app.use('/api/games', gameRoutes);
app.use('/api/leaderboard', leaderboardRoutes);

// 404处理
app.use((req, res, next) => {
  res.status(404).json({
    code: 404,
    message: '请求的资源不存在'
  });
});

// 错误处理中间件
app.use(errorHandler);

// 连接数据库并启动服务器
const PORT = process.env.PORT || 3001;

async function startServer() {
  try {
    // 测试数据库连接
    await db.sequelize.authenticate();
    console.log('数据库连接成功');
    
    // 测试Redis连接
    await redis.connect();
    console.log('Redis连接成功');
    
    // 同步数据库模型（开发环境可以使用sync）
    if (process.env.NODE_ENV === 'development') {
      await db.sequelize.sync({ alter: true });
      console.log('数据库模型同步完成');
    }
    
    // 启动服务器
    app.listen(PORT, () => {
      console.log(`服务器运行在 http://localhost:${PORT}`);
    });
  } catch (error) {
    console.error('启动服务器失败:', error);
    process.exit(1);
  }
}

// 启动服务器
startServer();

// 处理进程结束
process.on('SIGINT', async () => {
  try {
    await db.sequelize.close();
    await redis.quit();
    console.log('关闭数据库和Redis连接');
    process.exit(0);
  } catch (error) {
    console.error('关闭连接失败:', error);
    process.exit(1);
  }
});
